package com.ruoyi.tongban.service.impl;

import java.util.*;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

import com.google.gson.Gson;
import com.ruoyi.common.core.redis.RedisCache;
import com.ruoyi.common.utils.DateUtils;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.tongban.androidapi.domain.AndroidMessageBase;
import com.ruoyi.tongban.androidapi.domain.AndroidSendChildSignMessage;
import com.ruoyi.tongban.androidapi.domain.AndroidSocketSession;
import com.ruoyi.tongban.androidapi.util.AndroidSessionCache;
import com.ruoyi.tongban.domain.*;
import com.ruoyi.tongban.domain.face.UploadFaceData;
import com.ruoyi.tongban.domain.face.UploadRecordMessage;
import com.ruoyi.tongban.service.*;
import com.ruoyi.tongban.utils.QiniuCloudUtil;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import com.ruoyi.tongban.mapper.FaceSignMapper;
import org.springframework.transaction.annotation.Transactional;

/**
 * 考勤记录Service业务层处理
 * 
 * @author caiyanshan
 * @date 2021-04-08
 */
@Service
public class FaceSignServiceImpl implements IFaceSignService 
{
    private static final Logger logger = LoggerFactory.getLogger(FaceSignServiceImpl.class);
    
    @Autowired
    private FaceSignMapper faceSignMapper;
    
    @Autowired
    private IFacePersonService facePersonService;
    
    @Autowired
    private IFaceConfigService faceConfigService;
    
    @Autowired
    private IFaceSignDetailService faceSignDetailService;
    
    @Autowired
    private IFaceTvDeviceService faceTvDeviceService;
    
    @Autowired
    private RedisCache redisCache;
    
    private Lock lock = new ReentrantLock();


/*    public String selectFaceSignIds(int userType, Date searchTime){
        Map<String,Object> paramMap = new HashMap<String, Object>();
        paramMap.put("userType", userType);
        paramMap.put("searchTime", searchTime);
        List<FaceSign> faceSignList = faceSignMapper.selectFaceSignIds(paramMap);
        StringBuffer sb = new StringBuffer();
        for(int i = 0; i < faceSignList.size(); i++){
            sb.append(faceSignList.get(i).getUserId());
            if(i != faceSignList.size()-1){
                sb.append(",");
            }
        }
        return sb.toString();
    }*/

    /**
     * 查询考勤记录
     * 
     * @param recordId 考勤记录ID
     * @return 考勤记录
     */
    @Override
    public FaceSign selectFaceSignById(Long recordId)
    {
        return faceSignMapper.selectFaceSignById(recordId);
    }

    /**
     * 查询考勤记录列表
     * 
     * @param faceSign 考勤记录
     * @return 考勤记录
     */
    @Override
    public List<FaceSign> selectFaceSignList(FaceSign faceSign)
    {
        return faceSignMapper.selectFaceSignList(faceSign);
    }

    /**
     * 新增考勤记录
     * 
     * @param faceSign 考勤记录
     * @return 结果
     */
    @Override
    public int insertFaceSign(FaceSign faceSign)
    {
        faceSign.setCreateTime(DateUtils.getNowDate());
        return faceSignMapper.insertFaceSign(faceSign);
    }
    
    /**
     * 1、先根据设备序列号和设备上面的人员ID查找当前用户信息
     * 2、获取配置表中可以签到时间段，判断当前时间是否在时间段内(签到和签退)
     * 3、查找当天是否有签到记录，如果没有执行插入操作，有则执行更新操作
     * 4、把当前签到信息插入到详情表中
     */
    @Override
    @Transactional
    public boolean handleFaceSign(UploadFaceData.user message){
        lock.lock();
        try{
            Date nowDate = DateUtils.parseDate(message.getRecog_time());
            FaceSign faceSign = new FaceSign();
            String sn = message.getSn();
            String devicePersonId = message.getUser_id();
            Map<String, Object> paramMap = new HashMap<String, Object>();
            paramMap.put("devicePersonId", devicePersonId);
            paramMap.put("sn", sn);
            //1、查用户
            FacePerson facePerson = facePersonService.getDevicePersonDetail(paramMap);
            if(facePerson == null){//不存在该用户信息，不允许考勤
                Gson gson = new Gson();
                logger.error("not found the user info, the msg is : ");
                return false;
            }
            //2、固定格式"08:00-12:00","14:00-18:00",双字符串,中间用逗号分隔
            FaceConfig config = new FaceConfig();
            config.setConfigType("faceAuth");
            List<FaceConfig> faceConfigList = faceConfigService.selectFaceConfigList(config);
            String value = "";
            for(FaceConfig faceConfig : faceConfigList){
                value = faceConfig.getConfigValue();
            }
            if(StringUtils.isBlank(value)){//为空说明没有配置,那就不允许考勤
                Gson gson = new Gson();
                logger.error("not found the config time, the msg is : ");
                return false;
            }
            //TODO:后续可能会出中午签到和签退,暂不支持,如果要支持需改表结构
            String[] signTimes = value.split(",");
            Integer signFlag = -1;
            for(int i = 0; i < signTimes.length; i++){//0为签到，1为签退，
                String[] times = signTimes[i].split("-");
                Date startTime = DateUtils.dateTime("HH:mm", times[0]);
                Date endTime = DateUtils.dateTime("HH:mm", times[1]);
                //用设备传过来的时间,否则传递失败会造成漏签
                Date nowTime = DateUtils.dateTime("HH:mm", DateUtils.parseDateToStr("HH:mm", nowDate));
                if(DateUtils.isEffectiveDate(nowTime,startTime,endTime)){//有匹配,说明可以考勤
                    signFlag = i;
                }
            }
            if(signFlag == -1){//不在签到时间段,不可以提交数据
                return false;
            }
    
            //3、
            faceSign.setDeptId(facePerson.getDeptId());
            faceSign.setUserId(facePerson.getUserId());
            faceSign.setUserType(facePerson.getPersonType());
            faceSign.setCreateTime(nowDate);
            List<FaceSign> faceSignList = faceSignMapper.selectFaceSignList(faceSign);
            String photo = QiniuCloudUtil.upload64image(System.currentTimeMillis() + ".jpg", message.getPhoto());
            if(signFlag == 0){//上午
                faceSign.setSignIn(nowDate);
                faceSign.setInImage(photo);
            }else{//下午
                faceSign.setSignOut(nowDate);
                faceSign.setOutImage(photo);
            }
            if(faceSignList.size() == 0){//没有数据则插入数据
                faceSign.setUserName(facePerson.getUserName());
                faceSign.setDeptName(facePerson.getDeptName());
                faceSign.setGradeId(facePerson.getGradeId());
                faceSign.setGradeName(facePerson.getGradeName());
                faceSign.setClassId(facePerson.getClassId());
                faceSign.setClassName(facePerson.getClassName());
                faceSignMapper.insertFaceSign(faceSign);
            }else {
                faceSign.setRecordId(faceSignList.get(0).getRecordId());
                faceSign.setCreateTime(null);
                faceSignMapper.updateFaceSign(faceSign);
            }
            //4、
            FaceSignDetail faceSignDetail = new FaceSignDetail();
            faceSignDetail.setSn(message.getSn());
            faceSignDetail.setPersonId(message.getUser_id());
            //faceSignDetail.setIcCard(message.getData().getIcCard());
            faceSignDetail.setTemperature(message.getBody_temperature());
            /*faceSignDetail.setDetectType(message.getRecog_type());*/
            /*faceSignDetail.setDetectTime(message.getRecog_time());*/
            faceSignDetail.setPhoto(photo);
            faceSignDetail.setDetectScore(message.getConfidence());
            faceSignDetail.setRecordId(faceSign.getRecordId());
            faceSignDetailService.insertFaceSignDetail(faceSignDetail);
            if(facePerson.getPersonType() == 0){
                AndroidSendChildSignMessage androidSendChildSignMessage = new AndroidSendChildSignMessage();
                Map<String, Object> sendData = new HashMap<String, Object>();
                sendData.put("childId", facePerson.getUserId());
                if(signFlag == 0){//上午
                    sendData.put("signIn", DateUtils.getDate(DateUtils.YYYY_MM_DD_HH_MM_SS));
                }else{//下午
                    sendData.put("signOut", DateUtils.getDate(DateUtils.YYYY_MM_DD_HH_MM_SS));
                }
                androidSendChildSignMessage.setSignData(sendData);
                androidSendChildSignMessage.setFacePerson(facePerson);
                String key = "androidSendChildSignMessage:" + System.currentTimeMillis();
                redisCache.setCacheObject(key, androidSendChildSignMessage, 8, TimeUnit.HOURS);
            }
        }finally {
            lock.unlock();
        }
        return true;
    }
    

    
    /**
     * 1、先根据设备序列号和设备上面的人员ID查找当前用户信息
     * 2、获取配置表中可以签到时间段，判断当前时间是否在时间段内(签到和签退)
     * 3、查找当天是否有签到记录，如果没有执行插入操作，有则执行更新操作
     * 4、把当前签到信息插入到详情表中
     *//*
    @Override
    @Transactional
    public boolean handleFaceSign(UploadRecordMessage message){
        Date nowDate = new Date(message.getData().getDetectTime());
        FaceSign faceSign = new FaceSign();
        String sn = message.getSn();
        String devicePersonId = message.getData().getPersonId();
        Map<String, Object> paramMap = new HashMap<String, Object>();
        paramMap.put("devicePersonId", devicePersonId);
        paramMap.put("sn", sn);
        //1、查用户
        FacePerson facePerson = facePersonService.getDevicePersonDetail(paramMap);
        if(facePerson == null){//不存在该用户信息，不允许考勤
            Gson gson = new Gson();
            logger.error("not found the user info, the msg is : " + gson.toJson(message,UploadRecordMessage.class));
            return false;
        }
        //2、固定格式"08:00-12:00","14:00-18:00",双字符串,中间用逗号分隔
        FaceConfig config = new FaceConfig();
        config.setConfigType("timeInterval");
        List<FaceConfig> faceConfigList = faceConfigService.selectFaceConfigList(config);
        Integer week = DateUtils.dayForWeek(nowDate);
        String value = "";
        for(FaceConfig faceConfig : faceConfigList){
            if(week.toString().equals(faceConfig.getConfigKey())){
                value = faceConfig.getConfigValue();
                break;
            }
        }
        if(StringUtils.isBlank(value)){//为空说明没有配置,那就不允许考勤
            Gson gson = new Gson();
            logger.error("not found the config time, the msg is : " + gson.toJson(message,UploadRecordMessage.class));
            return false;
        }
        //TODO:后续可能会出中午签到和签退,暂不支持,如果要支持需改表结构
        String[] signTimes = value.split(",");
        Integer signFlag = -1;
        for(int i = 0; i < signTimes.length; i++){//0为签到，1为签退，
            String[] times = signTimes[i].split("-");
            Date startTime = DateUtils.dateTime("HH:mm", times[0]);
            Date endTime = DateUtils.dateTime("HH:mm", times[1]);
            //用设备传过来的时间,否则传递失败会造成漏签
            Date nowTime = DateUtils.dateTime("HH:mm", DateUtils.parseDateToStr("HH:mm", nowDate));
            if(DateUtils.isEffectiveDate(nowTime,startTime,endTime)){//有匹配,说明可以考勤
                signFlag = i;
            }
        }
        if(signFlag == -1){//不在签到时间段,不可以提交数据
            return false;
        }
    
        //3、
        faceSign.setDeptId(facePerson.getDeptId());
        faceSign.setUserId(facePerson.getUserId());
        faceSign.setUserType(facePerson.getPersonType());
        faceSign.setCreateTime(nowDate);
        List<FaceSign> faceSignList = faceSignMapper.selectFaceSignList(faceSign);
        if(signFlag == 0){//上午
            faceSign.setSignIn(nowDate);
        }else{//下午
            faceSign.setSignOut(nowDate);
        }
        String photo = QiniuCloudUtil.upload64image(System.currentTimeMillis() + ".jpg", message.getData().getPhoto());
        if(faceSignList.size() == 0){//没有数据则插入数据
            faceSign.setUserName(facePerson.getUserName());
            faceSign.setDeptName(facePerson.getDeptName());
            faceSign.setGradeId(facePerson.getGradeId());
            faceSign.setGradeName(facePerson.getGradeName());
            faceSign.setClassId(facePerson.getClassId());
            faceSign.setClassName(facePerson.getClassName());
            faceSign.setImage(photo);
            faceSignMapper.insertFaceSign(faceSign);
        }else {
            faceSign.setRecordId(faceSignList.get(0).getRecordId());
            faceSign.setImage(photo);
            faceSign.setCreateTime(null);
            faceSignMapper.updateFaceSign(faceSign);
        }
        //4、
        FaceSignDetail faceSignDetail = new FaceSignDetail();
        faceSignDetail.setSn(message.getSn());
        faceSignDetail.setPersonId(message.getData().getPersonId());
        faceSignDetail.setIcCard(message.getData().getIcCard());
        faceSignDetail.setTemperature(message.getData().getTemperature());
        faceSignDetail.setDetectType(message.getData().getDetectType());
        faceSignDetail.setDetectTime(message.getData().getDetectTime());
        faceSignDetail.setPhoto(photo);
        faceSignDetail.setDetectScore(message.getData().getDetectScore());
        faceSignDetail.setRecordId(faceSign.getRecordId());
        faceSignDetailService.insertFaceSignDetail(faceSignDetail);
        return true;
    }*/

    /**
     * 修改考勤记录
     * 
     * @param faceSign 考勤记录
     * @return 结果
     */
    @Override
    public int updateFaceSign(FaceSign faceSign)
    {
        return faceSignMapper.updateFaceSign(faceSign);
    }

    /**
     * 批量删除考勤记录
     * 
     * @param recordIds 需要删除的考勤记录ID
     * @return 结果
     */
    @Override
    public int deleteFaceSignByIds(Long[] recordIds)
    {
        return faceSignMapper.deleteFaceSignByIds(recordIds);
    }

    /**
     * 删除考勤记录信息
     * 
     * @param recordId 考勤记录ID
     * @return 结果
     */
    @Override
    public int deleteFaceSignById(Long recordId)
    {
        return faceSignMapper.deleteFaceSignById(recordId);
    }
}
